home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Disc to the Future 2
/
Disc to the Future Part II Programmer's Reference (Wayzata Technology)(6013)(1992).bin
/
MAC
/
THINKC
/
4_0
/
STANDALO
/
TOGSNDVO
/
TSV_SOUR
/
QUIK_FKE.C
next >
Wrap
C/C++ Source or Header
|
1991-02-11
|
14KB
|
686 lines
/* Quik FKEY Installer.c
⌐1991 by Mike Gleason Jr. */
#define NULL 0L
#define appleID 400
#define fileID 401
#define systemItem 1
#define suitcaseItem 2
#define quitItem 4
#define editID 402
#define SystemResFile 0
#define fkeyName "\pTogSndVol FKEY"
#define fkeyID 7
#define infoW 400
#define infoH 20
#define infoM 10
#define DO_NOT_REPLACE_EXISTING_RESOURCE 99
#define SFSaveDisk 0x214 /* Negative of current volume refnum [WORD] */
#define CurDirStore 0x398 /* DirID of current directory [LONG] */
#define MBarHeight 0x0baa
/* MAC GLOBALS: */
MenuHandle appleMenu, fileMenu, editMenu;
Rect dragRect;
WindowPtr InfoWindow;
Boolean gHasWaitNextEvent;
SysEnvRec gMac;
short mbarheight;
Rect WRect;
#pragma mark _protos
void main(void);
void InitMacintosh(void);
void InitVars(void);
void SetUpMenus(void);
int HandleEvent(void);
void HandleMouseDown(EventRecord *theEvent);
void HandleMenu (long mSelect);
void Message(char *str);
char *pStrcat(register char *s, register char *t);
char *pStrcpy(register char *s, register char *t);
OSErr SFGet(Str255 name, short *vref, long *dirid);
int SFPut(Str255 name);
short Install(int useSystemFile);
OSErr SFSystemDirectory(void);
OSErr SFDirID(int wd, int *volume, long *folder);
short CopyResource(short src, short dst, ResType type,
short srcID, short dstID);
void DelayUntilEvent(void);
void MiniDoAbout(char *info);
void main(void)
{
InitMacintosh();
InitVars();
SetUpMenus();
for (;;)
HandleEvent();
}
void InitMacintosh(void)
{
MaxApplZone();
InitGraf(&thePort);
InitFonts();
FlushEvents(everyEvent, 0);
InitWindows();
InitMenus();
TEInit();
InitDialogs(0L);
InitCursor();
SysEnvirons(1, &gMac);
#define WNETrapNum 0x60 /* Trap number of WaitNextEvent() */
#define UnImplTrapNum 0x9F /* Trap number "unimplemented trap" */
gHasWaitNextEvent = NGetTrapAddress(WNETrapNum, ToolTrap) !=
NGetTrapAddress(UnImplTrapNum, ToolTrap);
}
void InitVars(void)
{
mbarheight = * (short *) MBarHeight;
InfoWindow = NULL;
dragRect = screenBits.bounds;
InsetRect(&dragRect,5,5);
}
void SetUpMenus(void)
{
/* Make and insert menus: */
InsertMenu(appleMenu = NewMenu(appleID, "\p\024"), 0);
AppendMenu(appleMenu,"\pAbout Me╔;(-");
AddResMenu(appleMenu, 'DRVR');
InsertMenu(fileMenu = NewMenu(fileID, "\pFile"), 0);
AppendMenu(fileMenu, "\pInstall in System File;Install in a ╥Suitcase╙;(-;Quit/Q");
InsertMenu(editMenu = NewMenu(editID, "\pEdit"), 0);
AppendMenu(editMenu, "\pUndo/Z;(-;Cut/X;Copy/C;Paste/V;Clear/B");
/* Check the initial items that need to be: */
/* CheckItem(whatMenu, whichItem, boolean); */
DrawMenuBar();
}
int HandleEvent(void)
{
int ok;
EventRecord theEvent;
char ch;
if ( gHasWaitNextEvent ) {
ok = WaitNextEvent(everyEvent, &theEvent, 300, NULL);
}
else {
SystemTask();
ok = GetNextEvent(everyEvent, &theEvent);
}
if (ok)
switch (theEvent.what)
{
case mouseDown:
HandleMouseDown(&theEvent);
break;
case keyDown:
case autoKey:
ch = (char) (theEvent.message & charCodeMask);
if ((theEvent.modifiers & cmdKey) != 0)
HandleMenu(MenuKey(ch));
else
{
/* TEKey... */
}
break;
}
}
/* end HandleEvent */
void HandleMouseDown(EventRecord *theEvent)
{
WindowPtr theWindow;
int windowCode = FindWindow (theEvent->where, &theWindow);
switch (windowCode)
{
case inSysWindow:
SystemClick (theEvent, theWindow);
break;
case inMenuBar:
HandleMenu(MenuSelect(theEvent->where));
break;
}
}
/* end HandleMouseDown */
void HandleMenu (long mSelect)
{
int menuID = HiWord(mSelect);
int menuItem = LoWord(mSelect);
char name[255];
GrafPtr savePort;
WindowPeek frontWindow;
switch (menuID)
{
case appleID:
GetPort(&savePort);
GetItem(appleMenu, menuItem, name);
if (menuItem>1)
OpenDeskAcc(name);
else
{
/* Do 'About' item */
MiniDoAbout("\pQuikRez Installer\r⌐1991 Mike Gleason Jr.");
}
SetPort(savePort);
break;
case fileID:
switch (menuItem)
{
case systemItem:
Install(TRUE);
break;
case suitcaseItem:
Install(FALSE);
break;
case quitItem:
ExitToShell();
break;
}
break;
}; /* end of menu numbers */
HiliteMenu(0);
}
short Install(int useSystemFile)
{
OSErr err;
Str255 fkeyRsrcName, destName, srcName, defVolname, str;
short destResFile, srcResFile, oldResFile, vref, defVref;
short srcID, destID, preferredDstID, numFKEYs;
long dirid, defDirid;
register short i;
Handle fkey;
ResType type;
SetRect(&WRect, infoM, mbarheight+infoM,
infoM+infoW, mbarheight+infoM+infoH);
oldResFile = CurResFile();
InfoWindow = NewWindow
(
0L, /* window's storage ptr, 0L usually */
&WRect, /* the window's rect */
"\pWindow Title", /* the window's title */
FALSE, /* is the window initially visible? */
dBoxProc, /* type of window */
-1L, /* front of which window, -1L = all */
0, /* has a go away box? */
0 /* window refnum */
);
if (!InfoWindow) goto barf;
SetPort(InfoWindow);
ShowWindow(InfoWindow);
SelectWindow(InfoWindow);
err = HGetVol((StringPtr)defVolname, &defVref, &defDirid);
if (useSystemFile) destResFile = SystemResFile;
else
{
Message("\pSelect the file you want to install the FKEY in:");
if (SFSystemDirectory()) SysBeep(3L);
if (SFGet(destName, &vref, &dirid))
{
DisposeWindow(InfoWindow);
return (0);
}
destResFile = HOpenResFile(vref, dirid, destName, fsRdWrShPerm);
if (destResFile == -1 && ResError()) goto barf;
}
err = HSetVol(defVolname, 0, defDirid);
srcResFile = HOpenResFile(0, defDirid, fkeyName, fsRdPerm);
if (srcResFile == -1 && ResError())
{
/* our file wasn't in the defautlt directory. */
pStrcpy((char *) str, "\pPlease locate the file ╥");
pStrcat((char *) str, fkeyName);
pStrcat((char *) str, "\p.╙");
Message((char *) str);
* (short *)SFSaveDisk = -defVref;
* (long *)CurDirStore = defDirid;
if (SFGet(srcName, &vref, &dirid))
{
DisposeWindow(InfoWindow);
return (0);
}
srcResFile = HOpenResFile(vref, dirid, srcName, fsRdPerm);
if (srcResFile == -1 && ResError()) goto barf;
}
UseResFile(srcResFile);
numFKEYs = Count1Resources('FKEY');
for (i=0; i<numFKEYs; i++)
{
UseResFile(srcResFile);
SetResLoad(FALSE);
type = 'FKEY';
fkey = Get1IndResource(type, i+1);
if (err = ResError()) continue;
SetResLoad(TRUE);
GetResInfo(fkey, &srcID, &type, fkeyRsrcName);
if (err = ResError()) continue;
{
preferredDstID = srcID;
err = CopyResource(srcResFile, destResFile, type,
srcID, preferredDstID);
if (err != noErr && err != DO_NOT_REPLACE_EXISTING_RESOURCE)
goto puke;
else if (err == DO_NOT_REPLACE_EXISTING_RESOURCE)
{
short i;
for (i=5; i<=10; i++)
{
preferredDstID = i;
if (i == 10) preferredDstID = 0;
err = CopyResource(srcResFile, destResFile, type,
srcID, preferredDstID);
if (err != noErr && err != DO_NOT_REPLACE_EXISTING_RESOURCE)
goto puke;
else if (err == noErr)
{
/* Hey! We found a slot for the fkey to fit. */
/* Message */
break; /* done, finally! */
} /* end if we installed in an alternate slot */
} /* end looping for empty slots */
} /* end if our preferred slot was filled */
} /* end if we can copy the fkey into the dest */
if (err)
Message("\pSorry, there are already too many FKEYs in this file. <Click>");
else
{
char msg[256] = "\pInstalled ╥", tmp[8];
if (*fkeyName < 1) pStrcat(msg, "\pUntitled");
else pStrcat(msg, (char *) fkeyRsrcName);
pStrcat(msg, "\p╙ okay. Type command-shift-");
NumToString((long)preferredDstID, tmp);
pStrcat(msg, tmp);
pStrcat(msg, "\p to run it. <Click>");
Message(msg);
} /* end notifying the user of a successful install */
InvertRect(&InfoWindow->portRect);
DelayUntilEvent();
} /* end looping, copying all fkeys to dest. */
UseResFile(oldResFile);
if (srcResFile != SystemResFile) CloseResFile(srcResFile);
if (destResFile != SystemResFile) CloseResFile(destResFile);
DisposeWindow(InfoWindow);
return (1);
puke:
UseResFile(oldResFile);
if (srcResFile != SystemResFile) CloseResFile(srcResFile);
if (destResFile != SystemResFile) CloseResFile(destResFile);
Message("\pError occurred copying the FKEY.");
Delay(180, &dirid);
barf:
if (InfoWindow) DisposeWindow(InfoWindow);
SysBeep(3L);
return (0);
}
short CopyResource(short src, short dst, ResType type,
short srcID, short dstID)
{
Handle RSRC = 0L;
short oldResFile;
OSErr err;
Str255 resname;
oldResFile = CurResFile();
UseResFile(dst);
RSRC = Get1Resource(type, dstID);
/* see if we have a resource with
the same id already present. */
err = ResError();
if (!err && RSRC)
{
ReleaseResource(RSRC);
return (DO_NOT_REPLACE_EXISTING_RESOURCE);
}
UseResFile(src);
RSRC = Get1Resource(type, srcID);
/* load the source rsrc */
if (err = ResError()) goto heave;
GetResInfo(RSRC, &srcID, &type, resname);
/* we need to do this to get the
resource's name, if any */
if (err = ResError()) goto heave;
UseResFile(dst);
DetachResource(RSRC); /* have to detach it to make a copy */
AddResource(RSRC, type, dstID, resname);
/* now actually copy it */
if (err = ResError()) goto heave;
ChangedResource(RSRC); /* mark it as changed */
if (err = ResError()) goto heave;
UpdateResFile(dst); /* write out the resource file */
err = ResError();
ReleaseResource(RSRC); /* we don't need it any more */
heave:
UseResFile(oldResFile);
return (err);
} /* CopyResource */
void Message(char *str)
{
if (!InfoWindow) return;
SetPort(InfoWindow);
EraseRect(&InfoWindow->portRect);
TextFont(geneva);
TextSize(9);
MoveTo(10, 13);
DrawString(str);
ValidRect(&InfoWindow->portRect);
}
char *pStrcat(register char *s, register char *t)
{
register char *s2;
register short tLen;
s2 = s + *s;
*s += (tLen = *t);
for (++tLen; --tLen; s2[tLen] = t[tLen]);
return (char *) (s);
}
char *pStrcpy(register char *s, register char *t)
{
register short tLen;
for (tLen = *t + 1; tLen--; s[tLen] = t[tLen]);
return (char *) (s);
}
OSErr SFGet(Str255 name, short *vref, long *dirid)
{
SFReply reply;
SFTypeList typeList;
Point location = {0x40,0x40};
OSErr err;
location.v = mbarheight + infoH + (3*infoM);
SFGetFile(location, /* location */
"\pSpace for Rent", /* vestigial string */
NULL, /* fileFilter */
-1, /* numtypes; -1 means all */
&typeList, /* array to types to show */
NULL, /* dlgHook */
&reply); /* record for returned values */
if (reply.good)
{
pStrcpy((char *) name, (char *) reply.fName);
if (err = SetVol(name, reply.vRefNum)) return (err);
if (err = SFDirID(reply.vRefNum, vref, dirid)) return (err);
return (noErr);
}
else
return (1); /* nothing selected */
};
int SFPut(Str255 name)
{
SFReply reply;
Point location = {0x40,0x40};
OSErr err;
SFPutFile(location, /* location */
"\pSave document as:", /* prompt string */
name, /* original name */
NULL, /* dlgHook */
&reply); /* record for returned values */
if (reply.good)
{
pStrcpy((char *) name, (char *) reply.fName);
err = SetVol(name, reply.vRefNum);
return ((err == noErr));
}
else
return (FALSE);
};
OSErr SFSystemDirectory(void)
{
WDPBRec pb;
SysEnvRec theWorld;
Str255 name;
OSErr err;
#ifndef SFSaveDisk
#define SFSaveDisk 0x214 /* Negative of current volume refnum [WORD] */
#define CurDirStore 0x398 /* DirID of current directory [LONG] */
#endif
if (err = SysEnvirons(1, &theWorld))
return (err);
pb.ioNamePtr = (StringPtr) name;
pb.ioCompletion = 0L;
pb.ioVRefNum = theWorld.sysVRefNum;
pb.ioWDIndex = 0;
pb.ioWDProcID = 0;
pb.ioWDVRefNum = 0;
if ((err = PBGetWDInfo(&pb,false)))
return (err);
*(long *)CurDirStore = pb.ioWDDirID;
*(short *)SFSaveDisk = -pb.ioWDVRefNum;
/* on the next SFGetFile (╔) it will open in the System Folder. */
return (noErr);
} /* SFSystemDirectory */
OSErr SFDirID(int wd, int *volume, long *folder)
{
WDPBRec pb;
char name[72];
OSErr err;
pb.ioNamePtr = (StringPtr)name;
pb.ioVRefNum = wd;
pb.ioWDIndex = 0;
pb.ioWDProcID = 0;
pb.ioWDVRefNum = 0;
err = PBGetWDInfo(&pb, false);
if (err) return (err);
*volume = pb.ioWDVRefNum;
*folder = pb.ioWDDirID;
return (noErr);
} /* SFDirID */
void DelayUntilEvent(void)
{
EventRecord E;
int quikMask = keyDownMask + autoKeyMask + mDownMask;
/* delay until the mouse button is pressed, or a key is pressed */
/* ...and multifinder friendly, too! */
while (1)
{
if (GetNextEvent(quikMask, &E))
break;
SystemTask();
}
}
void MiniDoAbout(char *info)
{
WindowPtr AboutWindow;
Rect ARect = {0, 0, 64, 256};
GrafPtr oldPort;
EventRecord E;
int quikMask = keyDownMask + autoKeyMask + mDownMask;
int width, height;
GetPort(&oldPort);
/* Center the rectangle on the screen */
height = (ARect.bottom - ARect.top);
width = (ARect.right - ARect.left);
ARect.left = (screenBits.bounds.right - width) / 2;
ARect.right = ARect.left + width;
ARect.top = (screenBits.bounds.bottom - height) / 3; /* Apple's╔ */
ARect.bottom = ARect.top + height;
AboutWindow = NewWindow
(
0L, /* window's storage ptr, 0L usually */
&ARect, /* the window's rect */
"\pWindow Title", /* the window's title */
0, /* is the window initially visible? */
altDBoxProc, /* type of window */
-1L, /* front of which window, -1L = all */
0, /* has a go away box? */
0 /* window refnum */
);
if (!AboutWindow) return;
ShowWindow(AboutWindow);
SetPort(AboutWindow);
SelectWindow(AboutWindow);
ARect = AboutWindow->portRect;
EraseRect(&ARect);
InsetRect(&ARect, 10, 10);
TextFont(0);
TextSize(12);
TextFace(italic);
TextBox(info+1, (long) *info, &ARect, teJustLeft);
while (1)
{
if (GetNextEvent(quikMask, &E))
break;
SystemTask();
}
DisposeWindow(AboutWindow);
SetPort(oldPort);
} /* MiniDoAbout */